﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

using System.ComponentModel;
using System.Threading;
using System.Xml;



namespace GenerateDbApp
{



    class FileXML
    {
        private BackgroundWorker BW;
        private List<FileXMLRates> Rates;
        private static FileXML XML = null;

        private FileXML(BackgroundWorker BW_Temp)
        {
            BW = BW_Temp;
            Rates = new List<FileXMLRates>();
        }
        public static FileXML FileXMLMethod(BackgroundWorker BW_Temp)
        {
            if (XML == null)
                XML = new FileXML(BW_Temp);
            return XML;
        }
        public void ReadXML(string FileAdress)
        {
            string sLastName = "";
            string sLastCurrency = "";

            XmlTextReader Reader = new XmlTextReader(FileAdress);
            while (Reader.Read())
                switch (Reader.NodeType)
                {
                    case XmlNodeType.Element:
                        if (Reader.Name == "Rates")
                            Rates.Add(new FileXMLRates());
                        sLastName = Reader.Name;
                        break;

                    case XmlNodeType.Text:
                        if (sLastName == "DateTime")
                            Rates[Rates.Count - 1].SetDateTime(Reader.Value);
                        if (sLastName == "Currency")
                            sLastCurrency = Reader.Value;
                        if (sLastName == "Value")
                            Rates[Rates.Count - 1].CurrencyRates.Rate.Add(new FileXMLRate(sLastCurrency, Reader.Value));
                        break;
                }

            Rates.Sort(delegate(FileXMLRates x, FileXMLRates y) { return x.GetDateTime().CompareTo(y.GetDateTime()); });
        }
        public void AddToDbCommon()
        {
            using (ExtRatesEntities context = new ExtRatesEntities())
            {
                //clear table

                //Count
                for (int i = 0; i < 10; i++)
                {
                    DateTime Date = Convert.ToDateTime(Rates[i].GetDateTime());
                    DBWriter.GetDBWritter().WriteToPeriod(Date);
                    int PeriodId = context.Period.Where(c => c.DateTime == Date).FirstOrDefault().ID; 

                    for (int j = 0; j < Rates[i].CurrencyRates.Rate.Count; j++)
                    {
                        string sCur = Rates[i].CurrencyRates.Rate[j].GetCurrency();
                        if (context.Currency.Where(c => c.Name == sCur).SingleOrDefault() == null)
                            DBWriter.GetDBWritter().WriteToCurrency(Rates[i].CurrencyRates.Rate[j].GetCurrency());

                        int CurrencyId = context.Currency.Where(c => c.Name == sCur).FirstOrDefault().ID;
                        double ValueValue = Convert.ToDouble(Rates[i].CurrencyRates.Rate[j].GetValue().Replace(".", ","));

                        DBWriter.GetDBWritter().WriteToCurrencyRate(PeriodId, CurrencyId, ValueValue);
                    }
                }
            }
        }
        public void AddToDbCache()
        {
            DBDataDay Day = new DBDataDay();
            DBDataMonth Month = new DBDataMonth();
            DBDataYear Year = new DBDataYear();

            if (Rates.Count > 0)
            {
                for (int iCurrency = 0; iCurrency < Rates[0].CurrencyRates.Rate.Count; iCurrency++)
                    for (int iRate = 0; iRate < Rates.Count; iRate++)
                    {
                        double dValueNow = Convert.ToDouble(Rates[iRate].CurrencyRates.Rate[iCurrency].GetValue().Replace(".", ","));

                        //Day.Add(Rates[iRate].GetDateTime(), Rates[iRate].CurrencyRates.Rate[iCurrency].GetCurrency(), dValueNow);
                        Month.Add(Rates[iRate].GetDateTime(), Rates[iRate].CurrencyRates.Rate[iCurrency].GetCurrency(), dValueNow);
                        Year.Add(Rates[iRate].GetDateTime(), Rates[iRate].CurrencyRates.Rate[iCurrency].GetCurrency(), dValueNow);
                    }
               
                int i = 0, j = 0, k = 0, Pos = 0;
                int Frequency = 10;

                for (i = 0; i < Day.Item.Count; i++)
                {
                    Pos = 100 * (i + j + k) / (Day.Item.Count + Month.Item.Count + Year.Item.Count - 1);
                    AddToDbCachedItem("day", Frequency, Day.Item[i]);
                    BW.ReportProgress(Pos);
                }
                for (j = 0; j < Month.Item.Count; j++)
                {
                    Pos = 100 * (i + j + k) / (Day.Item.Count + Month.Item.Count + Year.Item.Count - 1);
                    AddToDbCachedItem("month", Frequency, Month.Item[j]);
                    BW.ReportProgress(Pos);
                }
                for (k = 0; k < Year.Item.Count; k++)
                {
                    Pos = 100 * (i + j + k) / (Day.Item.Count + Month.Item.Count + Year.Item.Count - 1);
                    AddToDbCachedItem("year", Frequency, Year.Item[k]);
                    BW.ReportProgress(Pos);
                }
            }
        }
        private void AddToDbCachedItem(string sPeriod, int iFrequency, DBData nNode)
        {
            if (nNode.Values.Count < iFrequency)
                iFrequency = nNode.Values.Count;
            double Koeficient = nNode.Values.Count / iFrequency;

            for (int Part = 0; Part < iFrequency; Part++)
            {
                double Medium = 0;
                for (int k = Convert.ToInt32(Math.Truncate(Part * Koeficient)); k < Convert.ToInt32(Math.Truncate((Part + 1) * Koeficient)); k++)
                    Medium = Medium + nNode.Values[k];

                Medium = Medium / (Convert.ToInt32(Math.Truncate((Part + 1) * Koeficient)) - Convert.ToInt32(Math.Truncate(Part * Koeficient)));

                if (sPeriod == "day")
                    DBWriter.GetDBWritter().WriteToDay(Convert.ToDateTime(nNode.GetDate()), nNode.GetCurrancy(), Medium);
                if (sPeriod == "week")
                    DBWriter.GetDBWritter().WriteToWeek(Convert.ToDateTime(nNode.GetDate()), nNode.GetCurrancy(), Medium);
                if (sPeriod == "month")
                    DBWriter.GetDBWritter().WriteToMonth(Convert.ToDateTime(nNode.GetDate()), nNode.GetCurrancy(), Medium);
                if (sPeriod == "year")
                    DBWriter.GetDBWritter().WriteToYear(Convert.ToDateTime(nNode.GetDate()), nNode.GetCurrancy(), Medium);
            }
        }
    }



}
